<?php
/**
 * Created by SendCouponsController.class.php.
 * User: wuxiang
 * Date: 2016/11/16
 * Time: 15:54
 */

namespace Coupons\Controller;


use Think\Controller;
use Common\Libiary\LogEX;

class SendCouponsController extends Controller
{
    const MAX_PROCESS_NUM = 10;
    const COUPONS_KEY = 'coupons:mobile:key';
    public $redis;

    public function __construct()
    {
        parent::__construct();
        $this->redis = $this->getRedis();
    }

    function index()
    {
        //处理业务代码

        while (true) {
            /**
             * fork是创建了一个子进程，父进程和子进程 都从fork的位置开始向下继续执行，
             * 不同的是父进程执行过程中，得到的fork返回值为子进程号，而子进程得到的是0
             *
             */
            $pid = pcntl_fork();
            if ($pid == -1) {
                $this->index();
            } elseif ($pid > 0) {
                static $execute = 0;
                $execute++;
                if($execute >= self::MAX_PROCESS_NUM) {
                    ////等待子进程中断，防止子进程成为僵尸进程。
                    pcntl_wait($status);
                    $execute--;
                }
            }else{
                //处理业务代码
                while(true) {
                    $mobieData = $this->getRedisData();
                    if($mobieData){
                        $this->sendCouponse($mobieData);
                    }
                    sleep(1);
                }
            }
        }
    }


    function sendCouponse($mobieData)
    {

        $sendCoupon = M('SendCoupon');
        foreach ($mobieData as $k => $v) {
            if (empty(isTelNumber($v['mobile']))) {
                $error['Mobile'] = $v['mobile'];
                $error['CouponId'] = $v['couponId'];
                $error['Status'] = 3;
                $error['CreateTime'] = time();
                $formatKey = $sendCoupon->add($error);
                if ($formatKey) {
                    LogEX::d('手机号格式错误' .'手机号'.$v['mobile']. '优惠券id'.$v['couponId'], $error);
                }
                continue;
            }
            //验证手机号是否是注册用户,如果不是注册用户，注册 15601723362
            $userId = isRegisterUser($v['mobile']);
            $res = [];
            if (empty($userId)) {
                //注册
                $userId = addRegisterUser($v['mobile']);
                if (empty($userId)) {
                    $res['Mobile'] = $v['mobile'];
                    $res['CouponId'] = $v['couponId'];
                    $res['Status'] = 1;
                    $res['CreateTime'] = time();
                    $primaryKey = $sendCoupon->add($res);
                    if ($primaryKey) {
                        LogEX::d('注册失败手机号' . '手机号'.$v['mobile']. '优惠券id'.$v['couponId'], $res);
                    }
                    continue;
                }
            }
            //发券处理
            $resCou = [];
            $resCou['Mobile'] = $v['mobile'];
            $resCou['CouponId'] = $v['couponId'];
            $resCou['Status'] = 2;
            $resCou['UserId'] = $userId;
            $resCou['CreateTime'] = time();
            $couponCode = sendCoupons($userId, $v['couponId'], $v['mobile']);
            if (empty($couponCode)) {
                $couponKey = $sendCoupon->add($resCou);
                if ($couponKey) {
                    LogEX::d('发送失败手机号' . '手机号'.$v['mobile']. '优惠券id'.$v['couponId'], $resCou);
                }
                continue;
            }
            $resCou['Status'] = 0;
            $resCou['CouponCode'] = $couponCode;
             LogEX::d('发送优惠券成功' . '手机号'.$v['mobile']. '优惠券id'.$v['couponId'].'优惠券码'.$couponCode, $resCou);
        }

    }


    //new redis
    function getRedis()
    {
        try {
            $redis = new \Redis;
            $redis->connect(REDIS_PUSH_TAGS, REDIS_PUSH_TAGS_PORT);
            $redis->auth(REDIS_PUSH_TAGS_AUTH);
            return $redis;
        } catch (\Exception $e) {
            $this->show('connect redis error:' . $e->getMessage(), 'ERR');
            sleep(1);
            return $this->getRedis();
        }
    }

    //获取数据
    function getRedisData()
    {
        try {
            $data = $this->redis->lPop(self::COUPONS_KEY);
            $result = json_decode($data, true);
            return $result;
        } catch (\Exception $e) {
            $this->show('get redis data:' . $e->getMessage(), 'ERR');
            $this->redis = $this->getRedis();
            sleep(1);
            return $this->getRedisData();
        }
    }

    function micrFloat()
    {
        return microtime(true);
    }

    //输出数据
    function show($msg, $level = 'DEBUG')
    {
        $msg = sprintf("[%s] %s\n", $level, $msg);
        echo $msg;
        //LogEX::i("MpushProcess",['data'=>$msg]);
    }

}